-
Notifications
You must be signed in to change notification settings - Fork 11.4k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
feat: subscription page #30551
feat: subscription page #30551
Conversation
🦋 Changeset detectedLatest commit: 4652b7f The changes in this PR will be included in the next version bump. This PR includes changesets to release 30 packages
Not sure what this means? Click here to learn what changesets are. Click here if you're a maintainer who wants to add another changeset to this PR |
Codecov Report
@@ Coverage Diff @@
## develop #30551 +/- ##
===========================================
- Coverage 51.34% 42.28% -9.06%
===========================================
Files 815 715 -100
Lines 15121 14078 -1043
Branches 2754 2692 -62
===========================================
- Hits 7764 5953 -1811
- Misses 6948 7778 +830
+ Partials 409 347 -62
Flags with carried forward coverage won't be shown. Click here to find out more. |
apps/meteor/client/views/admin/subscription/components/cards/AppsUsageCard.tsx
Show resolved
Hide resolved
apps/meteor/client/views/admin/subscription/components/cards/AppsUsageCard.tsx
Show resolved
Hide resolved
apps/meteor/client/views/admin/subscription/components/cards/MACCard.tsx
Show resolved
Hide resolved
c9ecb37
to
d870b4b
Compare
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Please check the comments and commits, I believe I solved all the issues that I pointed, but still I commented just to make you aware about the improvements
|
||
const CardTitle: FC = ({ children }) => ( | ||
<Box mbe={12} fontScale='h4' color='default'> | ||
const CardTitle: FC<ComponentProps<typeof Box>> = ({ children, ...props }) => ( |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think accepting properties here for styling violates our directives https://developer.rocket.chat/fuselage-design-system/componentization
const getHeaderButtons = () => { | ||
return ( | ||
<ButtonGroup> | ||
{isRegistered || (isRegistered && subscriptionSuccess) ? ( | ||
<Button icon={syncLicenseUpdate.isLoading ? undefined : 'reload'} onClick={() => handleSyncLicenseUpdateClick()}> | ||
{syncLicenseUpdate.isLoading ? <Throbber size='x12' inheritColor /> : t('Sync_license_update')} | ||
</Button> | ||
) : null} | ||
<UpgradeButton primary mis={8} i18nKey={isEnterprise ? 'Manage_subscription' : 'Upgrade'} /> | ||
</ButtonGroup> | ||
); | ||
}; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
there is no good reason to create a function to return this component
const getEnterpriseSectionContent = () => { | ||
const enterpriseModules = [ | ||
'scalability', | ||
'accessibility-certification', | ||
'engagement-dashboard', | ||
'oauth-enterprise', | ||
'custom-roles', | ||
'auditing', | ||
]; | ||
|
||
if (!isEnterprise) { | ||
return enterpriseModules.map((module) => { | ||
return { title: t(`UpgradeToGetMore_${module}_Title`), body: t(`UpgradeToGetMore_${module}_Body`) }; | ||
}); | ||
} | ||
|
||
const missingModules = enterpriseModules.filter((module) => !activeModules.includes(module)); | ||
|
||
return missingModules.map((module) => { | ||
return { | ||
title: t(`UpgradeToGetMore_${module}_Title`), | ||
body: t(`UpgradeToGetMore_${module}_Body`), | ||
}; | ||
}); | ||
}; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
why testing if its enterprise here? why not just filtering by the missing modulues?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
because the CE will not have modules
<Trans i18nKey='Compare_plans'> | ||
<Button is='a' external href={PRICING_LINK}> | ||
Compare plans | ||
</Button> | ||
</Trans> |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
t('Compare_plans')
|
||
return ( | ||
<FeatureUsageCard card={card}> | ||
{MACsCount !== undefined ? ( |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
if we dont have this info here, the parent page should be displaying the skeleton, no need to do this here
const pieGraph = macLimit && { | ||
used: macLimit?.value || 0, | ||
total: macLimit.max || 100, | ||
}; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
if you already tested macLimit
why macLimit?....
?
@@ -97,7 +97,7 @@ const InformationPage = memo(function InformationPage({ | |||
</Grid.Item> | |||
{!showSeatCap && ( | |||
<Grid.Item xl={12} height='50%'> | |||
<SeatsCard seatsCap={seatsCap} /> | |||
<SeatsCard /> |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think this is going to be 'loading' forever
const getLicenses = useEndpoint('GET', '/v1/licenses.info'); | ||
|
||
const queryClient = useQueryClient(); | ||
|
||
const notify = useSingleStream('notify-all'); | ||
|
||
useEffect(() => notify('license', () => invalidateQueryClientLicenses(queryClient)), [notify, queryClient]); | ||
|
||
return useQuery(['licenses', 'getLicenses'], () => getLicenses({}), { | ||
const queryKey = params?.loadValues ? ['licenses', 'getLicensesWithValues'] : ['licenses', 'getLicenses']; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
instead of using a different key why not just add a new parameter? this is going to break the invalidation
useEffect(() => { | ||
if (subscriptionSuccess && syncLicenseUpdate.isIdle) { | ||
syncLicenseUpdate.mutate(undefined, { onSuccess: () => refetchLicense() }); | ||
} | ||
}, [refetchLicense, subscriptionSuccess, syncLicenseUpdate]); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
this is the recipe to create a loop. also there is no need to refetch the license, the license is invalidated through the stream
export type BillingEndpoints = { | ||
'/v1/billing.checkoutUrl': { | ||
GET: () => { url: string }; | ||
}; | ||
}; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
no need to add this type here, this is supposed to be something internal so we can declare it using augmentation
if (!response.ok) { | ||
throw new Error(await response.json()); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@ggazzo I could not reproduce a scenario that got this error, because I didn't find a ok
attribute in the payload ... Is this going to work? Maybe I've missed something
{isLicenseLoading && <SubscriptionPageSkeleton />} | ||
{!isLicenseLoading && ( |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I know that some people prefer this way, but following our recommended best practices, this is not recommended...
https://alexkondov.com/tao-of-react/#conditional-rendering
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
they suggests ternary to avoid zeros but here we are handling booleans we should be fine :)
</CardBody> | ||
{showUpgradeButton && ( | ||
<CardFooter> | ||
{' '} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Is this necessary?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
not really, prettier doing pretty stuff
apps/meteor/client/views/admin/subscription/components/cards/ActiveSessionsPeakCard.tsx
Show resolved
Hide resolved
apps/meteor/client/views/admin/subscription/components/cards/FeaturesCard.tsx
Show resolved
Hide resolved
Co-authored-by: Kevin Aleman <[email protected]>
Proposed changes (including videos or screenshots)
New Manage subscription page to allow admin users check usage of some services and manage the subscription of the workspace
Changes:
Front-end:
Manage subscription
admin pageFramedIcon
component inui-client
package, should be moved to fuselage in the futureBox
component props toCard
components to give more flexibility on styling card elements due to design specsuseIsSelfHosted.ts
hook to check if server is running on cloud or notuseLicense.ts
hook to use the newlicense.info
endpointgetDaysLeft.ts
util function to check quantity of days given a specific dategetPlanName.ts
util function to retrieve the plan of the license given some condition related to activeModules, this function is necessary to prevent code repetitionuseAdministrationItems.spec.ts
unit testuseActiveConnections
hook tohooks
folder to be reused in other placesuseAnalyticsObject.ts
hook touseStatistics.ts
to better describe its usage and moved to more appropiate folderhooks
useCheckoutURL.ts
to get the new endpointhttps://billing.rocket.chat/v2/checkout
Back-end:
billing.checkoutUrl
to get the checkout url provided by cloudgetCheckoutUrl.ts
to fetch data from new billing serviceTODO:
license.info
endpoint instead oflicense.get
MACCard
andCountMACCard
(waiting feat: Save visitor's activity on agent's interaction #30222 to be merged)Issue(s)
Steps to test or reproduce
Further comments
NBJ-289